package com.rykj.base.refreshview.impl;

import com.rykj.api.ApiFailAction;
import com.rykj.api.ApiSuccessAction;
import com.rykj.base.refreshview.data.IDataSource;
import com.rykj.model.entity.ResultBase;
import com.rykj.util.LogX;
import com.rykj.util.RxUtil;

import rx.Observable;
import rx.Subscription;
import rx.functions.Action1;
import rx.subscriptions.CompositeSubscription;

/**
 * Description: author: zhangsan on 2017/8/16 下午3:28.
 */

public abstract class RxResultBaseDataSource<Data> implements IDataSource<ResultBase<Data>> {


//    protected ApiService apiService;

    protected CompositeSubscription mCompositeSubscription;


//    public RxDataSource(ApiService apiService) {
//        this.apiService = apiService;
//    }

//    @Override
//    public void requestData(int loadAction, IDataSourceResultHandler<Data> handler) {
//        startRequest(loadAction, fetchData(loadAction, handler), handler);
//    }


    @Override
    public void requestData(int loadAction, IDataSourceResultHandler<ResultBase<Data>> handler) {
        startRequest(loadAction, fetchData(loadAction, handler), handler);
    }

    @Override
    public void cancel() {
        unSubscribe();
    }

    protected void unSubscribe() {
        if (mCompositeSubscription != null) {
            mCompositeSubscription.unsubscribe();
        }
    }

    protected void startRequest(final int loadAction, Observable<ResultBase<Data>> dataObservable, final IDataSourceResultHandler<ResultBase<Data>> handler) {
        if (handler == null) {
            return;
        }
        Action1<Throwable> throwableAction1 = new ApiFailAction() {
            @Override
            public void call(Throwable throwable) {
                super.call(throwable);
                handler.handleError(throwable);
            }
        };
        Action1<ResultBase<Data>> dataAction1 = new ApiSuccessAction<ResultBase<Data>>() {

            @Override
            public void onSuccess(ResultBase<Data> result) {
                handler.handleResult(loadAction, result);
            }

            @Override
            public void onFail(int erroCode, String msg) {
                super.onFail(erroCode, msg);
                handler.handleErrorMsg(erroCode, msg);

                LogX.d("onFail() called with: erroCode = [" + erroCode + "], erroMsg = [" + msg + "]");
            }
        };
        Subscription subscription = dataObservable.compose(RxUtil.normalSchedulers()).subscribe(dataAction1, throwableAction1);
        addSubscrebe(subscription);
    }

    protected abstract Observable<ResultBase<Data>> fetchData(int loadType, IDataSourceResultHandler<ResultBase<Data>> handler);

    protected void addSubscrebe(Subscription subscription) {
        if (mCompositeSubscription == null) {
            mCompositeSubscription = new CompositeSubscription();
        }
        mCompositeSubscription.add(subscription);
    }
}
